package com.find.jwt.filter;

import io.jsonwebtoken.Claims;
import io.jsonwebtoken.Jws;
import io.jsonwebtoken.Jwts;
import org.springframework.security.authentication.UsernamePasswordAuthenticationToken;
import org.springframework.security.core.GrantedAuthority;
import org.springframework.security.core.authority.AuthorityUtils;
import org.springframework.security.core.context.SecurityContextHolder;
import org.springframework.web.filter.GenericFilterBean;

import javax.servlet.*;
import javax.servlet.http.HttpServletRequest;
import java.io.IOException;
import java.util.List;

/**
 * @ClassName JwtFilter
 * @Description 访问系统的时候效验token
 * @Author find me
 * @Date 2020/6/25 0025 17:53
 * @Version 1.0
 */
public class JwtFilter extends GenericFilterBean {
    /**
     * 用户每次登录的时候校验token
     *
     * @param servletRequest
     * @param servletResponse
     * @param filterChain
     * @throws IOException
     * @throws ServletException
     */
    @Override
    public void doFilter(ServletRequest servletRequest, ServletResponse servletResponse,
                         FilterChain filterChain) throws IOException, ServletException {
        HttpServletRequest req = (HttpServletRequest) servletRequest;
        // token 放在很多地方都可以，此处是默认把token放到请求头中
        String jwtToken = req.getHeader("authorization");
        // 解析token
        Jws<Claims> jws = Jwts.parser().setSigningKey("findme") // 生成token的签名
                .parseClaimsJws(jwtToken.replace("Bearer", "")); // 前端的token会自动加一个Bearer，此处需要去掉
        Claims claims = jws.getBody(); // 登录的信息
        String username = claims.getSubject();// 用户名 刚才在生成的时候放入了
        // 拿到登录的角色后要转换成一个list集合解析  此处是当前用户的角色
        List<GrantedAuthority> authorities = AuthorityUtils.commaSeparatedStringToAuthorityList((String) claims.get("authorities"));
        // new 一个新的token
        UsernamePasswordAuthenticationToken token = new UsernamePasswordAuthenticationToken(username, null, authorities);

        SecurityContextHolder.getContext().setAuthentication(token);
        // 对过滤器放行
        filterChain.doFilter(servletRequest, servletResponse);
    }

}